#include<sys/types.h>
#include<netinet/in.h>
#include<arpa/inet.h>
#include<sys/socket.h>
#include<sys/event.h>
#include<sys/time.h>
#include<cstring>
#include<cstdlib>
#include<iostream>
using namespace std;


int CreateListener(unsigned short Port);
int CreateQueue();
int AddEvent(int QueueFd, int Fd, int Filter);
int HandleEvent(int QueueFd, struct kevent& event);


int main()
{
    int ListenFd = CreateListener(1234);
    int QueueFd = CreateQueue();
    if( ListenFd < 0 || QueueFd < 0 )
    {
        perror("fatal");
        return -1;
    }

    int ret = AddEvent(QueueFd, ListenFd, EVFILT_READ | EVFILT_WRITE);
    if( ret < 0 )
    {
        cerr<<"AddEvent fail"<<endl;
        return -2;
    }

    while(1)
    {
        struct timespec timeout;
        memset(&timeout, 0 , sizeof(timeout));
        timeout.tv_sec =2;

        struct kevent myevents[10];

        int ret = kevent(QueueFd, NULL, 0, myevents, 10, &timeout);
        if( ret <= 0 )
            continue;

        for(int i =0; i<ret; ++i)
        {
            if( myevents[i].ident != ListenFd )
            {
                HandleEvent(QueueFd, myevents[i]);
            }
            else
            {
                int clientfd = accept(ListenFd, NULL, NULL);

                if( clientfd < 0 )
                    continue;

                AddEvent(QueueFd, clientfd, EVFILT_WRITE | EVFILT_READ);
            }
        }

    }
}

int CreateListener(unsigned short Port)
{
    int sockfd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
    if( sockfd < 0 )
        return -1;

    struct sockaddr_in listenaddr;
    memset(&listenaddr, 0 , sizeof(listenaddr));

    listenaddr.sin_family = AF_INET;
    listenaddr.sin_port = htons(Port);

    if( bind( sockfd, reinterpret_cast<struct sockaddr *>(&listenaddr), sizeof(listenaddr))< 0)
        return -2;

    return sockfd;
}

int CreateQueue()
{
    return kqueue();
}

int AddEvent(int QueueFd, int Fd, int Filter)
{
}
int HandleEvent(int QueueFd, struct kevent& event);


